package cn.thoughtworks.school.programCenter.services;

import cn.thoughtworks.school.programCenter.entities.MyWorkspace;
import cn.thoughtworks.school.programCenter.entities.Organization;
import cn.thoughtworks.school.programCenter.entities.Program;
import cn.thoughtworks.school.programCenter.entities.User;
import cn.thoughtworks.school.programCenter.entities.commands.CreateUserOrganization;
import cn.thoughtworks.school.programCenter.feign.OrganizationCenterFeign;
import cn.thoughtworks.school.programCenter.repositories.MyWorkspaceRepository;
import cn.thoughtworks.school.programCenter.repositories.ProgramRepository;
import cn.thoughtworks.school.programCenter.util.Roles;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.data.domain.Page;
import org.springframework.data.domain.Pageable;
import org.springframework.stereotype.Service;

import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.stream.Collectors;

@Service
public class OrganizationService {

  @Autowired
  private ProgramRepository programRepository;
  @Autowired
  private UserCenterService userCenterService;
  @Autowired
  private OrganizationCenterFeign organizationCenterFeign;
  @Autowired
  protected MyWorkspaceRepository myWorkspaceRepository;
  @Value("${feign.organizationCenter.url}")
  private String url;

  public Page<Program> getProgramsByOrganizationId(User user, Pageable pageable) {
    Long organizationId = userCenterService.getUserCurrentOrganizationId(user.getId());
    return programRepository.findByAvailableIsTrueAndOrganizationId(organizationId, pageable);
  }

  public void addUserOrganization(Long organizationId, Long userId) {
    Map userOrganization = new HashMap();
    userOrganization.put("userId", userId);
    userOrganization.put("organizationId", organizationId);

    organizationCenterFeign.addUserOrganization(userOrganization);

    userCenterService.updateUserCurrentOrganizationId(userId, new CreateUserOrganization(userId, organizationId));

  }

  public Page<Program> getWorkspaceByOrganizationId(User current, Pageable pageable) {
    Long userCurrentOrganizationId = userCenterService.getUserCurrentOrganizationId(current.getId());
    List<Long> myWorkspaceIds = myWorkspaceRepository.findByUserId(current.getId())
      .stream()
      .map(MyWorkspace::getProgramId)
      .collect(Collectors.toList());
    return programRepository.findByOrganizationIdAndIdIn(userCurrentOrganizationId, myWorkspaceIds, pageable);
  }

  public List<Organization> getOrganizationsByUserId(Long userId) {
    return organizationCenterFeign.getOrganizationsByUserId(userId);
  }

  public List<Organization> getOrganizationsByUserIdAndRole(Long userId, String role) {
    List<Organization> organizations = organizationCenterFeign.getOrganizationsByUserId(userId);
    Integer roleNumber = Roles.get(role);
    List<Long> organizationIds = userCenterService.findUserRolesByUserId(userId)
      .stream().filter(userRole -> Integer.valueOf(userRole.get("role").toString()).equals(roleNumber))
      .map(userRole -> Long.valueOf(userRole.get("organizationId").toString()))
      .collect(Collectors.toList());

    return organizations.stream()
      .filter(organization -> organizationIds.contains(organization.getId()))
      .collect(Collectors.toList());
  }

}
